package com.wxyzz.cem.service;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.plugins.pagination.PageDTO;
import com.baomidou.mybatisplus.extension.service.IService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.baomidou.mybatisplus.extension.toolkit.Db;
import com.wxyzz.cem.enums.ThreadLocalName;
import com.wxyzz.cem.exception.ClassInfoServiceException;
import com.wxyzz.cem.exception.UserServiceException;
import com.wxyzz.cem.mapper.ClassInfoMapper;
import com.wxyzz.cem.mapper.UserMapper;
import com.wxyzz.cem.pojo.ClassInfo;
import com.wxyzz.cem.pojo.User;
import com.wxyzz.cem.pojo.enums.ClassStatus;
import com.wxyzz.cem.pojo.enums.UserRole;
import com.wxyzz.cem.pojo.enums.UserStatus;
import com.wxyzz.cem.util.ThreadLocalUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import sun.text.resources.FormatData;

import java.text.DecimalFormat;
import java.util.List;

/**
 * <p>
 * 班级 服务实现类
 * </p>
 *
 * @author xc
 * @since 2024-07-04
 */
@Service
public class ClassInfoService extends ServiceImpl<ClassInfoMapper, ClassInfo> implements IService<ClassInfo> {
    @Autowired
    UserMapper userMapper;

    @Autowired
    UserService userService;
    public boolean addClassInfo(ClassInfo classInfo) {
        User user = ThreadLocalUtil.get(ThreadLocalName.USER.getValue(), User.class);
        if (user.getClassId() != null || user.getRole() != UserRole.USER) {
            throw new ClassInfoServiceException("该用户已加入班级");
        }

        classInfo.setUserId(user.getId());
        // 保留两位小数
        Float formatAmount = Float.parseFloat(new DecimalFormat("0.00").format(classInfo.getBalance()));
        classInfo.setBalance(formatAmount);
        this.save(classInfo);

        LambdaQueryWrapper<ClassInfo> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ClassInfo::getUserId, user.getId());
        ClassInfo one = this.getOne(queryWrapper);
        if (one == null) {
            return false;
        }

        user.setClassId(one.getId());
        user.setRole(UserRole.CLASS_ADMIN);
        Db.updateById(user);

        return true;
    }
    public boolean updateClassInfo(ClassInfo classInfo) {
        return this.updateById(classInfo);
    }

    public void joinClassById(User user, Integer classId) {
        if (user.getClassId() != null) {
            throw new UserServiceException("UserServiceException", "该用户已加入班级");
        }
        
        // 更新班级人数
        ClassInfo classInfo = this.getById(classId);
        classInfo.setSize(classInfo.getSize() + 1);
        this.updateById(classInfo);
        
        user.setClassId(classInfo.getId());
        userMapper.updateById(user);
    }

    public void exitClass(User user) {
        if (user.getClassId() == null){
            throw new UserServiceException("UserServiceException", "该用户未加入班级");
        }
        // 退出更新班级人数
        ClassInfo classInfo = this.getById(user.getClassId());
        classInfo.setSize(classInfo.getSize() - 1);
        this.updateById(classInfo);
        
        UpdateWrapper<User> userUpdateWrapper = new UpdateWrapper<>();
        userUpdateWrapper.lambda()
                .eq(User::getId, user.getId())
                .set(User::getClassId, null)
                .set(User::getRole, UserRole.USER);
        userMapper.update(null, userUpdateWrapper);
    }


    public boolean banClassById(Integer classId) {
        QueryWrapper<ClassInfo> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq(true,"id",classId);
        ClassInfo classInfo = this.getOne(queryWrapper);
        if (classInfo.getStatus() == ClassStatus.DISABLE){
            throw new UserServiceException("UserServiceException", "该班级已禁封");
        }
        classInfo.setStatus(ClassStatus.DISABLE);
        return this.updateById(classInfo);
    }

    public boolean unbanClassById(Integer id) {
        QueryWrapper<ClassInfo> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq(true,"id",id);
        ClassInfo classInfo = this.getOne(queryWrapper);
        if (classInfo.getStatus() == ClassStatus.ENABLE){
            throw new UserServiceException("UserServiceException", "该班级已解封");
        }
        classInfo.setStatus(ClassStatus.ENABLE);
        return this.updateById(classInfo);
    }


    public PageDTO<User> getClassMemberById(Integer classId, Integer page, Integer size, String name, String account, String phone) {
        QueryWrapper<User> classQueryWrapper = new QueryWrapper<>();
        classQueryWrapper.eq("class_id",classId);
        classQueryWrapper.like(name!=null,"name",name);
        classQueryWrapper.like(account!=null,"account",account);
        classQueryWrapper.like(phone!=null,"phone",phone);
        IPage<User> iPage = userMapper.selectPage(new Page<>(page,size), classQueryWrapper);
        PageDTO<User> pageDTO = new PageDTO<>();
        BeanUtil.copyProperties(iPage,pageDTO);
        return pageDTO;
    }



    private Integer fromTokenGetClassId() {
        //        从Token中获取用户id
        Integer userId = ThreadLocalUtil.get(ThreadLocalName.USER.getValue(), User.class).getId();
        User user;
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq(true,"id",userId);
        user = userMapper.selectOne(queryWrapper);
//        获取当前用户班级id
        Integer classId = user.getClassId();
        return classId;
    }

    public PageDTO<ClassInfo> getClassList(Integer page, Integer pageSize, String name, List<Integer> ids) {
        QueryWrapper<ClassInfo> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().like(name!=null,ClassInfo::getName,name);
        queryWrapper.lambda().in(ids != null && !ids.isEmpty(),ClassInfo::getId,ids);
        IPage<ClassInfo> iPage = this.page(new Page<>(page,pageSize), queryWrapper);
        PageDTO<ClassInfo> pageDTO = new PageDTO<>();
        BeanUtil.copyProperties(iPage,pageDTO);
        return pageDTO;
    }

    public boolean deleteClass(Integer id) {
        UpdateWrapper<User> updateWrapper = new UpdateWrapper<>();
        updateWrapper.lambda().eq(User::getClassId,id);
        updateWrapper.lambda().set(User::getClassId,null).set(User::getRole,UserRole.USER);
        userService.update(updateWrapper);
        return this.removeById(id);
    }
}
